Pass profile env vars to build commands
authorAlex Crichton <alex@alexcrichton.com>
Thu, 11 Sep 2014 15:09:47 +0000 (08:09 -0700)
committerAlex Crichton <alex@alexcrichton.com>
Mon, 15 Sep 2014 18:47:31 +0000 (11:47 -0700)
Closes #553

src/cargo/ops/cargo_rustc/context.rs
src/cargo/ops/cargo_rustc/mod.rs
src/doc/native-build.md
tests/test_cargo_compile.rs

index bb5e88301feb7694fe451f9f4065de378c0e80f4..2cb50d3976ccb110ff4ddb71d14fa4fc66c3b9d8 100644 (file)
@@ -22,8 +22,8 @@ pub struct Context<'a, 'b> {
     pub resolve: &'a Resolve,
     pub sources: &'a SourceMap<'b>,
     pub compilation: Compilation,
+    pub env: &'a str,
 
-    env: &'a str,
     host: Layout,
     target: Option<Layout>,
     target_triple: String,
index d53736aa4f71301a413a7312f7bfa01f581ffe1a..ab155d31faf7ce4e9dbc439434afbfef35a69f6c 100644 (file)
@@ -170,6 +170,15 @@ fn compile<'a, 'b>(targets: &[&'a Target], pkg: &'a Package,
 
 fn compile_custom(pkg: &Package, cmd: &str,
                   cx: &Context, first: bool) -> CargoResult<Work> {
+    let root = cx.get_package(cx.resolve.root());
+    let profile = root.get_manifest().get_targets().iter()
+                      .find(|target| target.get_profile().get_env() == cx.env)
+                      .map(|target| target.get_profile());
+    let profile = match profile {
+        Some(profile) => profile,
+        None => return Err(internal(format!("no profile for {}", cx.env)))
+    };
+
     // TODO: this needs to be smarter about splitting
     let mut cmd = cmd.split(' ');
     // TODO: this shouldn't explicitly pass `KindTarget` for dest/deps_dir, we
@@ -180,7 +189,10 @@ fn compile_custom(pkg: &Package, cmd: &str,
     let mut p = process(cmd.next().unwrap(), pkg, cx)
                      .env("OUT_DIR", Some(&output))
                      .env("DEPS_DIR", Some(&output))
-                     .env("TARGET", Some(cx.target_triple()));
+                     .env("TARGET", Some(cx.target_triple()))
+                     .env("DEBUG", Some(profile.get_debug().to_string()))
+                     .env("OPT_LEVEL", Some(profile.get_opt_level().to_string()))
+                     .env("PROFILE", Some(profile.get_env()));
     for arg in cmd {
         p = p.arg(arg);
     }
index 6fa5d97407dabe0fdbbbb2935ce7c1d619bdaed6..60a169487eeb724178e1475bdcf4e9514778f117 100644 (file)
@@ -78,6 +78,14 @@ commands.
                          directory in which all the output of the dependency's
                          build command was placed. This is useful for picking up
                          things like header files and such from other packages.
+* `CARGO_MANIFEST_DIR` - The directory containing the manifest for the package
+                         being built.
+* `OPT_LEVEL`, `DEBUG` - values of the corresponding variables for the
+                         profile currently being built.
+* `PROFILE` - name of the profile currently being built (see
+              [profiles][profile]).
+
+[profile]: manifest.html#the-[profile.*]-sections
 
 # A complete example
 
index 5809dc331da5be67fa48a64e83853316f6daebe0..03b3c3dfd26921bbb0fb649290842da32bfcf306 100644 (file)
@@ -793,6 +793,15 @@ test!(custom_build_env_vars {
             use std::io::fs::PathExtensions;
             fn main() {{
                 let _ncpus = os::getenv("NUM_JOBS").unwrap();
+                let debug = os::getenv("DEBUG").unwrap();
+                assert_eq!(debug.as_slice(), "true");
+
+                let opt = os::getenv("OPT_LEVEL").unwrap();
+                assert_eq!(opt.as_slice(), "0");
+
+                let opt = os::getenv("PROFILE").unwrap();
+                assert_eq!(opt.as_slice(), "compile");
+
                 let out = os::getenv("OUT_DIR").unwrap();
                 assert!(out.as_slice().starts_with(r"{0}"));
                 assert!(Path::new(out).is_dir());
@@ -800,6 +809,11 @@ test!(custom_build_env_vars {
                 let out = os::getenv("DEP_BAR_BAR_OUT_DIR").unwrap();
                 assert!(out.as_slice().starts_with(r"{0}"));
                 assert!(Path::new(out).is_dir());
+
+                let out = os::getenv("CARGO_MANIFEST_DIR").unwrap();
+                let p1 = Path::new(out);
+                let p2 = os::make_absolute(&Path::new(file!()).dir_path().dir_path());
+                assert!(p1 == p2, "{{}} != {{}}", p1.display(), p2.display());
             }}
         "#,
         p.root().join("target").join("native").display()));